/* (C) Copyright 2008 Bill Buckels */

/*
   TIME0A.c by bill buckels

   reward module for module 0 of "What Time is It"
   June 1991


*/



#include <stdio.h>
#include <fcntl.h>
#include <prodos.h>
#include <sgtty.h>
#include <device.h>
#include <sysfunc.h>


/* the auxmem (ems) library info */
/* graphics library map for library TIME.RIB */

/* lib info for character array created from fragment ELBOW.RAG */
#define ELBOW_SIZE   96
#define ELBOW_WIDTH  4
#define ELBOW_HEIGHT 24
#define ELBOW_OFFSET 15516

/* lib info for character array created from fragment ELBOW2.RAG */
#define ELBOW2_SIZE   96
#define ELBOW2_WIDTH  4
#define ELBOW2_HEIGHT 24
#define ELBOW2_OFFSET 15612

/* lib info for character array created from fragment DOWNPIPE.RAG */
#define DOWNPIPE_SIZE   64
#define DOWNPIPE_WIDTH  4
#define DOWNPIPE_HEIGHT 16
#define DOWNPIPE_OFFSET 15708

/* lib info for character array created from fragment DOWN2.RAG */
#define DOWN2_SIZE   64
#define DOWN2_WIDTH  4
#define DOWN2_HEIGHT 16
#define DOWN2_OFFSET 15772

/* lib info for character array created from fragment SPOUT.RAG */
#define SPOUT_SIZE   496
#define SPOUT_WIDTH  16
#define SPOUT_HEIGHT 31
#define SPOUT_OFFSET 15836

/* lib info for character array created from fragment SPOUT2.RAG */
#define SPOUT2_SIZE   496
#define SPOUT2_WIDTH  16
#define SPOUT2_HEIGHT 31
#define SPOUT2_OFFSET 16332

/* lib info for character array created from fragment WAVE.RAG */
#define WAVE_SIZE   1704
#define WAVE_WIDTH  24
#define WAVE_HEIGHT 71
#define WAVE_OFFSET 16828

/* lib info for character array created from fragment WAVENO.RAG */
#define WAVENO_SIZE   1704
#define WAVENO_WIDTH  24
#define WAVENO_HEIGHT 71
#define WAVENO_OFFSET 18532


/* the coordinates for the spout sections */
int spoutrasters[10]=
             {
               24,
               48,
               64,
               80,
               96,
               112,
               128,
               144,
               160,
               120};


extern int soundflag;

#define PUT 0    /* action verbs for putimage */
#define GET 1    /* expand as required */
#define P_STIX  2
#define P_BLACK 3
#define P_WHITE 4
#define P_AND   5
#define P_XOR   6


/* here we go lubey loo */

char loobey1[]={
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x05, 0x05,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x08, 0x0B,
            0xff, 0xff, 0xff};

char loobey2[]={
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x05, 0x05,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x03, 0x0B,
            0xff, 0xff, 0xff};

char loobey3[]={
            0x03, 0x08, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x0A, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x08, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x06, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x05, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x03, 0x02,
            0xff, 0xff, 0xff};

char loobey4[]={
            0x03, 0x08, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x0A, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x08, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x06, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x05, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x03, 0x02,
            0x07, 0x00, 0x01,
            0x03, 0x01, 0x0B,
            0xff, 0xff, 0xff};


ovmain()
{
       int answers=0;
       char *temp;
       unsigned char octave,note;


       /* backup the screen */
       emsputimage(WAVENO_OFFSET,
                   WAVENO_WIDTH,WAVENO_HEIGHT,
                   16,spoutrasters[9],GET);

       /* make waves */

       do
       {
       dospout(answers);
       emsupimage(WAVE_OFFSET,
                   WAVE_WIDTH,WAVE_HEIGHT,
                   16,spoutrasters[9],P_AND);


       if(!soundflag)sound(7,0,10);
       else
       {
       switch(answers)
       {
         case 0:
         case 2:  temp=(char *)&loobey1[0];break;
         case 1:  temp=(char *)&loobey2[0];break;
         case 5:  temp=(char *)&loobey4[0];break;
         default :temp=(char *)&loobey3[0];
        }
        while((octave=*temp++)!=0xFF)
        {
        note=*temp++;
        sound(octave,note,*temp);
        *temp++;
        }
       }

       /*clean up the wave */
       emsputimage(WAVENO_OFFSET,
                   WAVENO_WIDTH,WAVENO_HEIGHT,
                   16,spoutrasters[9],PUT);
       answers++;
       }while(answers<6);


return(0);

}

dospout(answers)
int answers;
{

    int i;
    switch(answers)
    {

      case 0  :    /* empty the elbow         */
                   emsputimage(ELBOW_OFFSET,
                   ELBOW_WIDTH,ELBOW_HEIGHT,
                   0,spoutrasters[0],PUT);
                   break;
      case 1  :
                    /* empty a single segment  */
                   emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[1],PUT);
                    /* empty a single segment  */
                   emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[2],PUT);
                   break;

                    /* empty a single segment  */
      case 2  :    emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[3],PUT);
                   emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[4],PUT);
                   break;

      case 3  :
                    /* empty a single segment  */
                   emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[5],PUT);
                   emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[6],PUT);
                   break;
      case 4  :
                    /* empty a single segment  */
                   emsputimage(DOWNPIPE_OFFSET,
                   DOWNPIPE_WIDTH,DOWNPIPE_HEIGHT,
                   0,spoutrasters[7],PUT);
                   break;

      case 5  :    /* empty the bottom        */
                   emsputimage(SPOUT_OFFSET,
                   SPOUT_WIDTH,SPOUT_HEIGHT,
                   0,spoutrasters[8],PUT);
                   break;

    }

}


/* special version of putimage loads from the bottom up */

/* emsupimage() */
/* handles screen manipulation of image fragments             */
/* both gets and puts and uses auxmem (ems) memory for the IO buffer   */
/* for screen puts other than memory moves a buffer is used   */

/* since a full screen stored in our .BOT format has a
   file size of 7680 bytes there is room in the upper ram bank
   to store 6 full screens (6x7680=46080 bytes) */


extern unsigned HB[];

emsupimage(emsarraybase,width,height,xorg,yorg,action)
unsigned emsarraybase;
int width,height,xorg,yorg,action;
{
   int ctr;
   char *ptr,*ptr2;
   int temp;
   /* the auxmem (ems) buffer starts above the 2nd page of text screen */
   /* in auxilliary memory */

   unsigned hitemp=emsarraybase+0x0C00+(width*height)-width;
   int bos=yorg+height-1;
   char tempbyte='\x00';
   char arrayname[40] ;

   if(action==P_WHITE)tempbyte='\xff';


   while(bos>=yorg)
   {
     temp = HB[bos];

     ptr = (char *)&arrayname[0];
     ptr2 = (char *)(temp+xorg);

     /* expand action verbs as required */
     switch(action)
     {
        case P_XOR  : /* reverse video */
                      auxtomain(hitemp,hitemp+width-1,&arrayname[0]);

                      for(ctr=0;ctr<width;ctr++)
                      {
                       *ptr2=(*ptr^0x7f);
                       *ptr2++;
                       *ptr++;
                       }
                       break;


                      /* bitwise ANDing the background... */
                      /* works best with white */
        case P_AND  :
                      auxtomain(hitemp,hitemp+width-1,&arrayname[0]);

                      for(ctr=0;ctr<width;ctr++)
                      {
                       *ptr2|=*ptr;
                       *ptr2++;
                       *ptr++;
                       }
                       break;

                      /* if the image byte is black don't erase the */
                      /* background                                 */
        case P_STIX :
                      auxtomain(hitemp,hitemp+width-1,&arrayname[0]);

                      for(ctr=0;ctr<width;ctr++)
                      {
                        tempbyte=*ptr++;
                        if(tempbyte=='\x80'||tempbyte=='\x00')*ptr2++;
                        else *ptr2++=tempbyte;
                        }
                      break;

                   /* clear an area the size of the image fragment */
                   /* to black or white */
        case P_BLACK:
        case P_WHITE:
                      for(ctr=0;ctr<width;ctr++)*ptr2++=tempbyte;break;


                  /* read each raster into auxmem (ems) */
        case GET:  maintoaux((temp+xorg),(temp+xorg+width-1),hitemp);
                   break;

        case PUT: /* read each raster to the screen */
        default :  auxtomain(hitemp,hitemp+width-1,(temp+xorg));
                   break;
     }
     bos--;
     hitemp-=width;
     }
}

